using System;
using System.Drawing;
using System.Drawing.Printing;
using System.IO;
using System.Windows.Forms;
using C1.C1Report;
using Microsoft.Office.Interop.Excel;
using PCSUtils.Framework.ReportFrame;
using PCSUtils.Utils;
using System.Data;
using System.Data.OleDb;
using System.Reflection;
using C1.Win.C1Preview;
using C1PrintPreviewDialog = PCSUtils.Framework.ReportFrame.C1PrintPreviewDialog;
using DataTable = System.Data.DataTable;

namespace BangThanhToanTienLuong
{
	[Serializable]
	public class BangThanhToanTienLuong : MarshalByRefObject, IDynamicReport
	{
		public BangThanhToanTienLuong()
		{
		}

		private string mConnectionString;
		private ReportBuilder mReportBuilder;
		private C1PrintPreviewControl mReportViewer;
		private object mResult;

		/// <summary>
		/// ConnectionString, provide for the Dynamic Report
		/// ALlow Dynamic Report to access the DataBase of PCS
		/// </summary>
		public string PCSConnectionString
		{
			get { return mConnectionString; }
			set { mConnectionString = value; }
		}

		/// <summary>
		/// Report Builder Utility Object
		/// Dynamic Report can use this object to render, modify, layout the report
		/// </summary>
		public ReportBuilder PCSReportBuilder
		{
			get { return mReportBuilder; }
			set { mReportBuilder = value; }
		}

		/// <summary>
		/// ReportViewer Object, provide for the DynamicReport, 
		/// allow Dynamic Report to manipulate with the REportViewer, 
		/// modify the report after rendered if needed
		/// </summary>
		public C1PrintPreviewControl PCSReportViewer
		{
			get { return mReportViewer; }
			set { mReportViewer = value; }
		}

		/// <summary>
		/// Store other result if any. Ussually we store return DataTable here to display on the ReportViewer Form's Grid
		/// </summary>
		public object Result
		{
			get { return mResult; }
			set { mResult = value; }
		}

		private bool mUseReportViewerRenderEngine = false;

		/// <summary>
		/// Notify PCS whether the rendering report process is run by
		/// this IDynamicReport or the ReportViewer Engine (in the ReportViewer form)
		/// </summary>
		public bool UseReportViewerRenderEngine
		{
			get { return mUseReportViewerRenderEngine; }
			set { mUseReportViewerRenderEngine = value; }
		}

		private string mstrReportDefinitionFolder = string.Empty;
		/// <summary>
		/// Inform External Process where to find out the ReportLayout	 ( the PCS' ReportDefinition Folder Path )
		/// </summary>				
		public string ReportDefinitionFolder
		{
			get { return mstrReportDefinitionFolder; }
			set { mstrReportDefinitionFolder = value; }
		}


		private string mstrReportLayoutFile = string.Empty;		
		/// <summary>
		/// Inform External Process about the Layout file
		/// in which PCS instruct to use
		/// (PCS will assign this property while ReportViewer Form execute,
		/// ReportVIewer form will use the layout file in the report config entry to put in this property)
		/// </summary>		
		public string ReportLayoutFile
		{
			get 
			{
				return mstrReportLayoutFile;
			}
			set
			{
				mstrReportLayoutFile = value;
			}
		}


		public object Invoke(string pstrMethod, object[] pobjParameters)
		{
			return this.GetType().InvokeMember(pstrMethod, BindingFlags.InvokeMethod, null, this, pobjParameters);
		}

		public DataTable ExecuteReport(string pstrMonth, string pstrYear, string pstrProductionLineID)
		{
			DataTable dtbReportData = GetReportData(pstrMonth, pstrYear, pstrProductionLineID);
			
			#region Init

			C1Report rptReport = new C1Report();
			if (mstrReportLayoutFile == null || mstrReportLayoutFile.Length == 0)
				mstrReportLayoutFile = "BangThanhToanTienLuong.xml";
			string[] arrstrReportInDefinitionFile = rptReport.GetReportInfo(mstrReportDefinitionFolder + "\\" + mstrReportLayoutFile);
			rptReport.Load(mstrReportDefinitionFolder + "\\" + mstrReportLayoutFile, arrstrReportInDefinitionFile[0]);
			arrstrReportInDefinitionFile = null;
			rptReport.Layout.PaperSize = PaperKind.A4;

			#endregion

			rptReport.DataSource.Recordset = dtbReportData;
			rptReport.Render();

			try
			{
				decimal decTotalAmount = decimal.Round(Convert.ToDecimal(rptReport.Fields["fldTotalAmount"].Value), 0);
				string strTotalAmountInWord = PCSUtils.Utils.ConvertNumberToWord.ChuyenSoThanhChu(decTotalAmount);
				rptReport.Fields["fldWord"].Text = strTotalAmountInWord;
			}
			catch{}
			try
			{
				rptReport.Fields["@year"].Text = pstrYear;
			}
			catch{}
			try
			{
				rptReport.Fields["@month"].Text = pstrMonth;
			}
			catch{}
			try
			{
				rptReport.Fields["@year"].Text = pstrYear;
			}
			catch{}

			rptReport.Render();
            C1PrintPreviewDialog ppvViewer = new C1PrintPreviewDialog();
			ppvViewer.FormTitle = rptReport.Fields["fldTitle"].Text;
			ppvViewer.ReportViewer.NavigationPanelVisible = false;
			ppvViewer.ReportViewer.Document = rptReport.Document;
			ppvViewer.Show();

			return dtbReportData;
		}

		private DataTable GetReportData(string pstrMonth, string pstrYear, string pstrProductionLineID)
		{
			OleDbConnection cn = null;
			try
			{
				cn = new OleDbConnection(mConnectionString);
				DataTable dtbItem = new DataTable();
				string strSql = " Select SOD.Fgoodscode, SOD.WOQuantity qty, M.ProductionLineID,getDate() ServerDate, PL.Name PL,"
					+ "  DATEPART(year, D.RequestDate)years, DATEPART(month, D.RequestDate) months,"
					+ " SUM(D.ApprovalAmount) +"
					+ " ISNULL((Select Sum(ApprovalAmount) from PAY_AdditionSalaryDetail AD"
					+ " INNER JOIN PAY_AdditionSalaryMaster AM ON AM.AdditionSalaryMasterID=AD.AdditionSalaryMasterID"
					+ " WHERE DATEPART(year, D.RequestDate)=DATEPART(year, AD.RequestDate)"
					+ " AND DATEPART(Month, D.RequestDate)=DATEPART(Month, AD.RequestDate)"
					+ " AND Am.ProductionLineID = M.ProductionLineID"
					+ " AND AM.SaleOrderDetailID = M.SaleOrderDetailID ),0)Amount,"
					+ " I.Code PartNo, I.Description PartName"
					+ " FROM PAY_PaymentRequestDetail D "
					+ " JOIN PAY_PaymentRequestMaster M"
					+ " ON D.PaymentRequestMasterID = M.PaymentRequestMasterID"
					+ " INNER JOIN SO_SaleOrderDetail SOD ON SOD.SaleorderdetailID=M.SaleorderdetailID"
					+ " INNER JOIN PRO_ProductionLine PL ON PL.ProductionLineID=M.ProductionLineID"
					+ " INNER JOIN ITM_Product I ON I.ProductID=SOD.ProductID"
					+ " WHERE DATEPART(year, TransDate)= " + pstrYear
					+ " And DATEPART(month, TransDate)= " + pstrMonth
					+ " And M.ProductionLineID= " + pstrProductionLineID
					+ " And SOD.FgoodsCode<>'VV_TTK'"
					+ " GROUP BY M.SaleOrderDetailID, SOD.Fgoodscode, SOD.WOQuantity, M.ProductionLineID, PL.Name, "
					+ " DATEPART(year, D.RequestDate), DATEPART(month, D.RequestDate), I.Code, I.Description"
					+ " UNION ALL"
					+ " Select SOD.FgoodsCode,Null qty,M.ProductionLineID,getDate() ServerDate, PL.Name PL, "
					+ "  DATEPART(year, D.RequestDate)years, DATEPART(month, D.RequestDate) months,D.ApprovalAmount Amount,"
					+ " '' PartNo,"
					+ " d.Reason PartName"
					+ " FROM PAY_AdditionSalaryDetail D"
					+ " INNER JOIN PAY_AdditionSalaryMaster M ON M.AdditionSalaryMasterID=D.AdditionSalaryMasterID"
					+ " INNER JOIN SO_SaleOrderDetail SOD ON SOD.SaleOrderDetailID=M.SaleOrderDetailID"
					+ " INNER JOIN PRO_ProductionLine PL ON PL.ProductionLineID=M.ProductionLineID"
					+ " WHERE SOD.FgoodsCode='VV_TTK'"
					+ " AND DATEPART(year, D.RequestDate)= " + pstrYear
					+ " And DATEPART(month, D.RequestDate)= " + pstrMonth
					+ " And M.ProductionLineID= " + pstrProductionLineID;
				OleDbDataAdapter odad = new OleDbDataAdapter(strSql, cn);
				odad.Fill(dtbItem);
				return dtbItem;
			}
			finally
			{
				if (cn != null)
					if (cn.State != ConnectionState.Closed)
						cn.Close();
			}
		}
	}
}